package com.marakana.obolo;

//Imports de Android

import java.util.Random;

import android.app.Activity;
import android.os.Bundle;

import android.graphics.Point;
import android.util.DisplayMetrics;

import graphics.FinishDialog;
import graphics.PanelGame;

import graphics.PanelCard;

// Imports de game
import game.Game;
import game.Obolo;
import game.Player;
import game.CPU;
import game.IAOboloHelp;

public class GameActivity extends Activity {
	private static Game game;
	private IAOboloHelp iaHelper;

	private static final int RIVAL_TURN = 0;
	private static final int USER_TURN = 1;

	private int[] backgrounds = { R.drawable.background_1,
			R.drawable.background_2, R.drawable.background_3 };

	private PanelCard oboloFromDeck;
	private PanelCard oboloFromBoard;
	private PanelCard[] rivalCards;
	private PanelCard[] userCards;
	private PanelCard[][] boardGame;


	private PanelGame panelGameActivity;

	/** Called when the activity is first created. */
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.game);

		// Captura de les variables que s'envien mitjan�ant un intent
		Bundle extras = getIntent().getExtras();
		int[] dimension = extras.getIntArray("dimension");
		String[] rules = extras.getStringArray("rules");
		Player user = (Player) extras.getSerializable("user");
		Player rival = (Player) extras.getSerializable("rival");

		// Controlar de que la dimensio s'hagi pasat correctament abans de crear
		// el game
		game = new Game(dimension[0], dimension[1], dimension[2]);

		// Afegir els components que necessita game per funcionar (Players y
		// Rules)
		game.setPlayers(rival, user);

		// Crea las normes per afegirlas a game
		game.setRules(rules);

		panelGameActivity = (PanelGame) findViewById(R.id.panelGameActivity);
		panelGameActivity.setGame(game);
		panelGameActivity.setGameActivity(this);
		Random idBackground = new Random();
		panelGameActivity.setBackgroundId(backgrounds[idBackground
				.nextInt(backgrounds.length)]);

		DisplayMetrics displaymetrics = new DisplayMetrics();
		getWindowManager().getDefaultDisplay().getMetrics(displaymetrics);
		panelGameActivity.setSize(displaymetrics.widthPixels,
				displaymetrics.heightPixels);

		// Omple de obolos els decks dels jugadors
		setCards(game.getPlayerDeck(Game.RIVAL), game.getPlayerDeck(Game.USER),
				game.getBoard());

		// Assigna el torn
		updateTurn(game.getTurn());

		// Comproba si hi ha alguna m�quina com a jugador i l'activa

		disablePlayers();

		for (int i = 0; i < 2; i++) {
			if (!game.getPlayer(i).isHuman()) {
				iaNextTurn();
			}
		}

	}

	public void setOboloFromDeck(PanelCard oboloFromDeck) {
		this.oboloFromDeck = oboloFromDeck;
	}

	public PanelCard getoboloFromDeck() {
		return oboloFromDeck;
	}

	public void setOboloFromBoard(PanelCard oboloFromBoard) {
		this.oboloFromBoard = oboloFromBoard;
	}

	public PanelCard getOboloFromBoard() {
		return oboloFromBoard;
	}
	
	private void disablePlayers() {
		panelGameActivity.disablePlayers(game.getPlayer(0), game.getPlayer(1));
	}

	private void setCards(Obolo[] rivalDeck, Obolo[] userDeck, Obolo[][] board) {
		rivalCards = new PanelCard[rivalDeck.length];
		userCards = new PanelCard[userDeck.length];
		boardGame = new PanelCard[board.length][];

		for (int position = 0; position < rivalDeck.length; position++) {
			rivalCards[position] = new PanelCard(rivalDeck[position], game.getPlayer(rivalDeck[position].getOwner()));
			rivalCards[position].setPlace(PanelCard.DECK_PLACE);
		}

		for (int position = 0; position < userDeck.length; position++) {
			userCards[position] = new PanelCard(userDeck[position], game.getPlayer(userDeck[position].getOwner()));
			userCards[position].setPlace(PanelCard.DECK_PLACE);
		}

		for (int row = 0; row < board.length; row++) {
			boardGame[row] = new PanelCard[board[row].length];
			for (int column = 0; column < board[row].length; column++) {
				boardGame[row][column] = new PanelCard(board[row][column], null);
				boardGame[row][column].setPlace(PanelCard.BOARD_PLACE);
				boardGame[row][column].setPositionOnBoard(new Point(row,column));
			}
		}
		panelGameActivity.setCards(rivalCards, userCards, boardGame);
	}

	public boolean hasTurn(int playerNumber) {
		if (game.getTurn() == playerNumber)
			return true;
		else
			return false;
	}

	private void updateTurn(int gameTurn) {
		if (gameTurn == Game.RIVAL) {
			/*
			 * txtPlayers[Game.RIVAL].setTextColor(Color.YELLOW);
			 * txtPlayers[Game.USER].setTextColor(Color.WHITE);
			 */			
		} else {

			/*
			 * txtPlayers[Game.USER].setTextColor(Color.YELLOW);
			 * txtPlayers[Game.RIVAL].setTextColor(Color.WHITE);
			 */			
		}
	}

	public void playObolo() {	
		Point boardPoint = new Point(oboloFromBoard.getPositionOnBoard().x, oboloFromBoard.getPositionOnBoard().y);
		try {			
			game.putObolo(boardPoint.x, boardPoint.y, oboloFromDeck.getObolo());

			oboloFromBoard.setObolo(game.getBoard()[boardPoint.x][boardPoint.y]);
			// Actualitza el estat del Obolo triat en el deck
			oboloFromDeck.setObolo(null);

			// oboloPressed.setBackgroundColor(Color.TRANSPARENT);

			// Mostra la norma activada
			/*
			 * Toast.makeText(this, "", Toast.LENGTH_LONG) .show();
			 */

			// Comproba si s'ha acabat la partida
			if (game.isFinish()) {
				// Acaba la partida
				// Es mira qui es el perdedor i qui el guanyador
				Player winner = game.whoWin();
				if (winner != null) {
					if (game.whoWin().equals(game.getPlayer(0))) {
						finishGame(game.getPlayer(0), game.getPlayer(1));
					} else {
						finishGame(game.getPlayer(1), game.getPlayer(0));
					}
				} else {
					finishGame(null, null);
				}

			} else {
				// oboloPressed.setOnTouchListener(null);
				oboloFromDeck = null;
				updateTurn(game.getTurn());
				// Comproba si ha de tirar la IA
				if (!game.getPlayer(game.getTurn()).isHuman())
					iaNextTurn();
			}
		} catch (IllegalArgumentException e) {

		}
	}

	protected void finishGame(Player winner, Player looser) {
		// Crea un Dialog
		FinishDialog finishDialog = null;

		if (winner == null)
			// Mostra el empat
			finishDialog = new FinishDialog(this);
		else {
			// Mostra el guanyador de la partida i deixa triar el premi
			finishDialog = new FinishDialog(this, winner, looser);
		}

		finishDialog.setOwnerActivity(this);
		finishDialog.setCancelable(true);
		finishDialog.setCanceledOnTouchOutside(true);
		finishDialog.show();
		// finish();
	}

	// Metode que fa tirar a la m�quina
	private void iaNextTurn() {
		iaHelper = ((CPU) game.getPlayer(game.getTurn())).bestOption(game);
		// Selecciona el obolo del deck que vol jugar
		for (int i = 0; i < game.getPlayerDeck(game.getTurn()).length; i++) {
			if (iaHelper.obolo == (game.getPlayerDeck(game.getTurn())[i])) {
				if (game.getTurn() == RIVAL_TURN) {
					oboloFromDeck = rivalCards[i];
					oboloFromDeck.setObolo(game.getPlayer(game.getTurn())
							.getObolo(i));
				} else {
					oboloFromDeck = userCards[i];
					oboloFromDeck.setObolo(game.getPlayer(game.getTurn())
							.getObolo(i));
				}
			}
		}
		// Selecciona la posicio del taulell a on jugara el Obolo
		for (int row = 0; row < boardGame.length; row++) {
			if (iaHelper.row == row) {
				for (int column = 0; column < boardGame[row].length; column++) {
					if (iaHelper.column == column) {
						oboloFromBoard = boardGame[row][column];
						playObolo();
					}
				}
			}
		}
	}
}
